let STA = require('STA');

cc.Class({
    extends: cc.Component,

    properties: {
        game:cc.Node,
        DefaultCube:cc.Prefab,
        chapterNumberLabel:cc.Node,
        animalMoveSound:{
            default:null,
            type:cc.AudioClip,
        },
        gameWinSound:{
            default:null,
            type:cc.AudioClip
        },
        gameWinPage:cc.Node,
        ribbonText:cc.Node,

        rankAvators:cc.Node,
    },

    onLoad () {
        STA.log("paintCubes - onload");
        STA.result = null;

        this.gameWinPage.active = false;

        this.startMs = new Date().getTime();
        this.animalName = STA.getAnimalName();
        this._game = this.game.getComponent("gamePlay");
        this._game.animalsNode.zIndex = 100;  // 使头尾不会被身体遮挡

        this.resultEnd = 3; // 默认提示结束位

        this.hasStart = false; // 是否已经开始
        this.isFading = false; // 是否正在褪去
        this.isMoving = false; // 是否正在移动
        this.isTiping = false; // 是否正在提示

        this.moveTipCubes = [];

        this.cubeGap = 20;  // 方块间隔
        this.cubeSize = 180;    // 方块大小
        this.maxCubesTotalHeight = 1000;  // 用于适配，游戏方块内容高度
        this.scaleForHeight = 1;  // 初始的高度缩放

        this.unit = this.cubeSize + this.cubeGap; //基准单位
        this.scale = 1; // 基准缩放

        this.baseWidth = 5; // 基准宽度
        this.link = []; // 已经过的方块列表

        this.animalBodiesPool = new cc.NodePool();  // 回收的身体对象池
        this.animalBodies = [];   // 使用中的身体列表
        this.animalHead = null;   // 动物头
        this.animalTail = null;    // 动物尾

        this.map = [];  // 方块地图
        this.chapterData = {  // 关卡初始化信息
            chapterNumber:null,
            height:1,
            width:4,
            startNode:{
                x:0,
                y:0
            },
            lacks:[]
        };

        this.loadChapter();
        this.gameScreenOnTouch();
        this.gameOnKeyBoard();
    },

    loadChapter(){ // 加载关卡
        this.chapterNumber = 15*(STA.bigChapterNumber-1) + STA.smallChapterNumber;
        this.chapterNumberLabel.getComponent(cc.Label).string = "第"+this.chapterNumber+"关";

        STA.log("paintCubes - loadChapter" + this.chapterNumber);
        let _this = this;
        cc.loader.loadRes ('chapters/' + this.chapterNumber, (err, data)=>{
            if(err) throw err;
            _this.chapterData = data.json;

            if(_this.chapterData.width>5){
                _this.scale = _this.baseWidth / _this.chapterData.width;  // 基于宽度的缩放
            }

            let cubesTotalHeight = _this.unit * _this.chapterData.height;
            if(cubesTotalHeight > this.maxCubesTotalHeight){     
                this.scaleForHeight = this.maxCubesTotalHeight / cubesTotalHeight; // 基于高度的缩放
            }

            _this.scale *= this.scaleForHeight;
            _this.cubeGap *= _this.scale;
            _this.cubeSize *= _this.scale;
            _this.unit *= _this.scale;
            _this.animalAdjustDistance = 3/7 * this.unit;

            let gameWidth = _this.chapterData.width * _this.unit - _this.cubeGap;
            let gameHeight = _this.chapterData.height * _this.unit - _this.cubeGap;
            _this.node.x += -1/2 * gameWidth + _this.unit/ 2 ;
            _this.node.y += 1/2 * gameHeight - _this.unit/ 2;

            _this.makeMap();
            _this.loadAnimal();
            _this.loadAnimalBody();                
        });
    },

    makeMap(){  // 根据关卡信息制作地图
        STA.log("paintCubes - makeMap");
        this.winNumber = this.chapterData.height * this.chapterData.width - this.chapterData.lacks.length;
        if(this.winNumber < 5){
            this.resultEnd = 2;  // 低级关卡补丁：不能提示到胜利
        }

        let startNode = this.chapterData.startNode;
        for(let i=0,l1=this.chapterData.height;i<l1;i++){
            this.map[i] = [];
            for(let j=0,l2=this.chapterData.width;j<l2;j++){
                if(!this.isLack(j,i)){
                    let cube = cc.instantiate(this.DefaultCube);
                    cube.width = this.cubeSize;
                    cube.height = this.cubeSize;
                    cube._x = j;
                    cube._y = i;
                    
                    if(i === startNode.y && j === startNode.x){   // 如果是起点
                        cube.index = 0;
                        this.link.push(cube);
                    }else{
                        cube.index = null;
                    }
                    this.map[i][j] = cube;
                    cube.dir = null;
                    cube.setPosition(j*(this.unit),-i*(this.unit));
                    this.node.addChild(cube);
                }
            }
        }
    },

    moveTip(isTouchEnd){ // 移动提示
        let _this = this;
        function _moveTip(theCube){
            if(theCube && theCube.index != 0 && !theCube.index){
                theCube.runAction(cc.scaleTo(0.1,9/10));
                _this.moveTipCubes.push(theCube);
            }
        }

        if(isTouchEnd){
            if(this.moveTipCubes.length){ // 松开后，让所有提示的缩小了的方块复原
                for(let cube of this.moveTipCubes){
                    cube.runAction(cc.scaleTo(0.1,1));
                }
                this.moveTipCubes = [];
            }
        }else{
            if(this.moveTipCubes.length) return;

            let head = this.link[this.link.length-1];
            let headX = head._x, headY = head._y;
            STA.log(headX, headY);
            // 分别判断上右下左四个方向是否可行
            if(headY > 0){
                let theCube = this.map[headY-1][headX];
                _moveTip(theCube);
            }
            if(headX < this.chapterData.width - 1){
                let theCube = this.map[headY][headX+1];
                _moveTip(theCube);
            }
            if(headY < this.chapterData.height - 1){
                let theCube = this.map[headY+1][headX];
                _moveTip(theCube);
            }
            if(headX > 0){
                let theCube = this.map[headY][headX-1];
                _moveTip(theCube);
            }
        }
    },

    loadAnimalBody(){  // 获取动物身体
        STA.log("paintCubes - loadAnimalBody");
        if(!this.bodySprite){
            cc.loader.loadRes("animalBodies/"+this.animalName,cc.SpriteFrame,(err,spriteFrame)=>{
                if(err) cc.error(err);
                this.bodySprite = spriteFrame;
                let theBody = this.makeAnimalBody();
                this.node.addChild(theBody);   // addChild 之后，修改 width 和 height 才能生效
                theBody.width = this.cubeSize;
                theBody.height = this.cubeSize;
                this.animalBodies.push(theBody); 
            });
        }
    },
    
    makeAnimalBody(){
        let startNode = this.chapterData.startNode;
        let theBody = new cc.Node();
        theBody.setPosition(startNode.x * this.unit,-startNode.y * this.unit);
        theBody.addComponent(cc.Sprite).spriteFrame = this.bodySprite;
        theBody.getComponent(cc.Sprite).type = cc.Sprite.Type.SLICED;
        return theBody;
    },

    loadAnimal(){ // 获取动物头尾
        STA.log("paintCubes - loadAnimal");
        
        let startNode = this.chapterData.startNode;
        this.animal = this._game.chooseAnimal(this.animalName);

        this.animalHead = this.animal.getChildByName('head');
        this.animalHead.setPosition(startNode.x * this.unit,-startNode.y * this.unit);
        this.animalHead.y -= this.animalAdjustDistance;
        this.animalHead.scale = this.scale * 1.1;
        this.animalHead.dir = 2;

        this.animalTail = this.animal.getChildByName('tail');
        this.animalTail.setPosition(startNode.x * this.unit,-startNode.y * this.unit);
        this.animalTail.y +=  this.animalAdjustDistance;
        this.animalTail.dir = 2;

        this.hasStart = true;

        this.loadAnimalHeadAnimations();
    },

    loadAnimalHeadAnimations(){
        let animationsKey = STA.getHeadAnimations(this.animalName);
        this.headDragon = this.animalHead.getComponent(dragonBones.ArmatureDisplay);
        this.headAnimations = this.headDragon.getAnimationNames(animationsKey);
        this.headBlink();
    },
    headBlink(){
        // STA.log("paintCubes - headBlink");
        this.headDragon.playAnimation(this.headAnimations[0],-1);
        this.headDragon.timeScale = 1;
    },
    headShake(){
        // STA.log("paintCubes - headShake");
        this.headDragon.playAnimation(this.headAnimations[1], -1);
        this.headDragon.timeScale = 1.5;
        this.headWaitBlinkTimeout = setTimeout(()=>{
            this.headBlink();
        },300);
    },

    isLack(x,y){    // 判断是否为缺失的方块
        for(let lack of this.chapterData.lacks){
            if(lack.x == x && lack.y == y){
                return true;
            }
        }
        return false;
    },

    gameScreenOnTouch(){   // 监听屏幕触摸事件
        STA.log("paintCubes - gameScreenOnTouch");

        let theFunction = (event)=>{
            if(!this.hasStart) return;
            if(this.isMoving) return;
            if(this.isFading) return;
            if(this.isTiping) return;

            let theTouch = this.node.convertTouchToNodeSpace(event.touch);
            let theX = Math.floor((theTouch.x + 1/2 * this.unit) / this.unit),
                theY = Math.floor(-(theTouch.y - 1/2 * this.unit) / this.unit);

            if(theY > -1 && theY < this.chapterData.height && theX > -1 && theX < this.chapterData.width){ // 边界判断
                if(this.map[theY] && this.map[theY][theX]){
                    let theCube = this.map[theY][theX];
                    let index = theCube.index;
                    if(index==0 || index){ // 如果已经路过
                        this.fadeCubes(index);
                    }else{
                        let head = this.link[this.link.length-1];
                        let needTip = true;
                        if(head._x == theX){
                            if(theY - head._y == 1){
                                this.moveToDir(theCube,2);
                                needTip = false;
                            }else if(theY - head._y == -1){
                                this.moveToDir(theCube,0);
                                needTip = false;
                            }
                        }else if(head._y == theY){
                            if(theX - head._x == 1){
                                this.moveToDir(theCube,1);
                                needTip = false;
                            }else if(theX - head._x == -1){
                                this.moveToDir(theCube,3);
                                needTip = false;
                            }
                        }
                        
                        if(needTip){  // 如果都不是可选的近邻，则要提示可选的近邻
                            this.moveTip();
                        }
                    }
                }
            }
        }

        this.game.on(cc.Node.EventType.TOUCH_START, theFunction);
        this.game.on(cc.Node.EventType.TOUCH_MOVE, theFunction);
        this.game.on(cc.Node.EventType.TOUCH_END, ()=>{
            this.moveTip(true);
            this.headShake();
        });
    },

    gameOnKeyBoard() { // 监听键盘事件，测试用
        cc.eventManager.addListener({
            event: cc.EventListener.KEYBOARD,
            onKeyPressed: (keyCode, event) => {
                this.keyHandler(keyCode);
            },
        }, this.node);
    },

    keyHandler(keyCode) {   // 实际键盘事件
        if(!this.hasStart) return;
        let _this = this;
        function _moveToDir(headX,headY,dir){
            let theCube = _this.map[headY][headX];
            if(theCube.index != 0 && !theCube.index){
                _this.moveToDir(theCube,dir);
            }
        }

        let head = this.link[this.link.length-1];
        switch (keyCode) {
            case cc.KEY.w:{
                if(head._y > 0 && !this.isLack(head._x,head._y-1)){
                    _moveToDir(head._x,head._y-1, 0);
                }
                break;
            }
            case cc.KEY.d:{
                if(head._x < this.chapterData.width - 1 && !this.isLack(head._x+1,head._y)){
                    _moveToDir(head._x+1,head._y, 1);
                }
                break;
            }
            case cc.KEY.s:{
                if(head._y < this.chapterData.height - 1 && !this.isLack(head._x,head._y+1)){
                    _moveToDir(head._x,head._y+1, 2);
                }
                break;
            }
            case cc.KEY.a:{
                if(head._x > 0 && !this.isLack(head._x-1,head._y)){
                    _moveToDir(head._x-1,head._y, 3);
                }
                break;
            }
            case cc.KEY.e:{
                this.fadeCubes(0);
                break;
            }
        }
    },

    moveToDir(theCube,dir){ // 向某个方向移动
        if(this.isMoving) return;
        this.isMoving = true;
        theCube.dir = dir;

        let theX = this.animalHead.x,
            theY = this.animalHead.y;

        if(dir == 0){
            theY += this.unit;
        }else if(dir == 1){
            theX += this.unit;
        }else if(dir == 2){
            theY -= this.unit;
        }else if(dir == 3){
            theX -= this.unit;
        }
        switch(this.animalHead.dir){
            case 0:{
                theY -= this.animalAdjustDistance;
                this.animalHead.y -= this.animalAdjustDistance;
                break;
            }
            case 1:{
                theX -= this.animalAdjustDistance;
                this.animalHead.x -= this.animalAdjustDistance;
                break;
            }
            case 2:{
                theY += this.animalAdjustDistance;
                this.animalHead.y += this.animalAdjustDistance;
                break;
            }
            case 3:{
                theX += this.animalAdjustDistance;
                this.animalHead.x += this.animalAdjustDistance;
                break;
            }
        }
        switch(dir){
            case 0:{
                theY += this.animalAdjustDistance;
                this.animalHead.y += this.animalAdjustDistance;
                break;
            }
            case 1:{
                theX += this.animalAdjustDistance;
                this.animalHead.x += this.animalAdjustDistance;
                break;
            }
            case 2:{
                theY -= this.animalAdjustDistance;
                this.animalHead.y -= this.animalAdjustDistance;
                break;
            }
            case 3:{
                theX -= this.animalAdjustDistance;
                this.animalHead.x -= this.animalAdjustDistance;
                break;
            }
        }
        this.animalHead.dir = dir;
        this.animalHead.runAction(cc.sequence(
            cc.moveTo(50/1000,theX,theY),
            cc.callFunc(()=>{
                this.isMoving = false;
            })
        ));

        this.hadMove(theCube);
    },

    hadMove(theCube){   // 完成移动后需要做的操作
        if(!this.hasStartMove){
            this.hasStartMove = true; // 开始移动则开始计时
            this.startTime = new Date().getTime();
        }

        // STA.playAudio(this.animalMoveSound);
        STA.playAudioBK("animalMove");

        this.animalHead.setRotation([180,270,0,90][theCube.dir]);

        this.tailAdjust(theCube.dir);
        let head = this.link[this.link.length-1];
        let currentBody = this.animalBodies[this.animalBodies.length-1];   // 此时的 currentBody 宽高都为不可见的状态
        currentBody.width = this.cubeSize;
        currentBody.height = this.cubeSize;

        if(theCube.dir == 0){
            currentBody.setPosition(head._x * this.unit, -head._y * this.unit + this.cubeGap);
            currentBody.height += this.unit;
            currentBody.y += (1/2 * this.unit - this.cubeGap);
        }else if(theCube.dir == 1){
            currentBody.setPosition(head._x * this.unit + this.cubeGap, -head._y * this.unit);
            currentBody.width += this.unit;
            currentBody.x += (1/2 * this.unit - this.cubeGap);
        }else if(theCube.dir == 2){
            currentBody.setPosition(head._x * this.unit, -head._y * this.unit - this.cubeGap);
            currentBody.height += this.unit;
            currentBody.y -= (1/2 * this.unit - this.cubeGap);
        }else if(theCube.dir == 3){
            currentBody.setPosition(head._x * this.unit - this.cubeGap, -head._y * this.unit);
            currentBody.width += this.unit;
            currentBody.x -= (1/2 * this.unit - this.cubeGap);
        }

        theCube.index = this.link.length;
        this.link.push(theCube);

        let theBody = null;
        if(this.animalBodiesPool.size()){
            theBody = this.animalBodiesPool.get();
        }else{
            theBody = this.makeAnimalBody();
        }

        this.node.addChild(theBody);
        theBody.getComponent(cc.Sprite).type = cc.Sprite.Type.SLICED;
        theBody.width = this.cubeSize;
        theBody.height = this.cubeSize;
        theBody.setPosition(theCube._x * this.unit, -theCube._y * this.unit);

        this.animalBodies.push(theBody);

        if(this.link.length === this.winNumber){
            this.gameWin();
        }
    },

    gameWin(){
        this.hasStart = false;

        this.endTime = new Date().getTime();
        let thePlayTime = this.endTime - this.startTime;

        let second = 1000;
        let theTime = Math.ceil(thePlayTime / second);
        let _this = this;
        setTimeout(()=>{
            if(theTime < 10){
                // 完美过关
                STA.perfectNumber++;
                localStorage.setItem("perfectNumber", STA.perfectNumber);

                if(!STA.perfectChapters[_this.chapterNumber]){
                    _this._game.tipFrame.active = true;
                    let _tipFrame = _this._game.tipFrame;
                    let tipText = _tipFrame.getChildByName("tip_text");
                    tipText.getComponent(cc.Label).string = `完美过关，获得100金币！`;
                    let btn = _tipFrame.getChildByName("orangeBtn");
                    btn.active = true;
                    btn.getChildByName("text").getComponent(cc.Label).string = "好";
                    btn.on(cc.Node.EventType.TOUCH_START, (event)=>{
                        btn.runAction(cc.sequence(
                            cc.scaleTo(0.15,1.1),
                            cc.scaleTo(0.15,1),
                            cc.callFunc(()=>{
                                _tipFrame.active = false;
                                btn.active = false;
                                _this.gameWinPage.active = true;
                            })
                        ));
                        STA.playAudio(_this._game.tapSound);
                    })
                    STA.increaseCoin(100);
                }else{
                    _this.gameWinPage.active = true;
                }

                STA.perfectChapters[_this.chapterNumber] = true;
                localStorage.setItem("perfectChapters", JSON.stringify(STA.perfectChapters));
            }else{
                _this.gameWinPage.active = true;
            }
        },500);

        _this.ribbonText.getComponent(cc.Label).string = 
            `用时${theTime}秒，击败了${(Math.random()*100).toFixed(2)}%的喵
            智商超过${parseInt(Math.random()*100000000)}位喵星人`;

        _this.gameWinTimeout = setTimeout(()=>{
            STA.playAudio(_this.gameWinSound);
        },500);

        STA.saveRankData(_this.startMs.toString(),_this.chapterNumber,()=>{
            _this.getSuccessAvatorRank();
        });
    },

    getSuccessAvatorRank(){
        if(!STA.isQQ) return;

        console.log("getSuccessAvatorRank");
        
        function loadImg(obj,url){
            cc.loader.load({url,type:'jpg'}, (err, texture)=>{
                if(err) throw err;
                let sprite = new cc.SpriteFrame(texture);
                obj.getComponent(cc.Sprite).spriteFrame = sprite;
            });
        }

        console.log("STA.isQQ - true");
        let avator1 = this.rankAvators.getChildByName("avator1"),
            avator2 = this.rankAvators.getChildByName("avator2"),
            avator3 = this.rankAvators.getChildByName("avator3");

        BK.QQ.getRankListWithoutRoom("score", 1, 0, (errCode, cmd, data)=>{
            // 返回错误码信息
            if (errCode !== 0) {
                STA.log('获取排行榜数据失败!错误码：' + errCode);
            }else if(data){
                STA.log('+++成功获取排行榜信息！');
                let list = data.data.ranking_list;

                let before = null, after = null, me = null;
                for(let i=0;i<list.length;i++){
                    if(list[i].selfFlag){
                        if(i==0){
                            avator1.active = false;
                        }else{
                            let img1 = avator1.getChildByName("imgMask").getChildByName("img");
                            loadImg(img1, before.url);
                            let nickname1 = avator1.getChildByName("nickname");
                            nickname1.getComponent(cc.Label).string = "第"+ before.score +"关";
                        }

                        me = list[i];
                        let img2 = avator2.getChildByName("imgMask").getChildByName("img");
                        loadImg(img2,me.url);
                        let nickname2 = avator2.getChildByName("nickname");
                        nickname2.getComponent(cc.Label).string = "第"+ me.score +"关";

                        if(list[i+1]){
                            after = list[i+1];
                            let img3 = avator3.getChildByName("imgMask").getChildByName("img");
                            loadImg(img3,after.url);
                            let nickname3 = avator3.getChildByName("nickname");
                            nickname3.getComponent(cc.Label).string = "第"+ after.score +"关";

                        }else{
                            avator3.active = false;
                        }

                    }else{
                        before = list[i];
                    }
                }
            }
        });
    },

    headAdjust(iniDir, dir){    // 骨骼动画，头部位置微调
        switch(iniDir){
            case 0:{
                this.animalHead.y -= this.animalAdjustDistance;
                break;
            }
            case 1:{
                this.animalHead.x -= this.animalAdjustDistance;
                break;
            }
            case 2:{
                this.animalHead.y += this.animalAdjustDistance;
                break;
            }
            case 3:{
                this.animalHead.x += this.animalAdjustDistance;
                break;
            }
        }
        switch(dir){
            case 0:{
                this.animalHead.y += this.animalAdjustDistance;
                break;
            }
            case 1:{
                this.animalHead.x += this.animalAdjustDistance;
                break;
            }
            case 2:{
                this.animalHead.y -= this.animalAdjustDistance;
                break;
            }
            case 3:{
                this.animalHead.x -= this.animalAdjustDistance;
                break;
            }
        }
        this.animalHead.dir = dir;
    },
    
    tailAdjust(dir){   // 骨骼动画，尾部位置微调
        if(this.link.length == 1){
            let startNode = this.chapterData.startNode;
            this.animalTail.setPosition(startNode.x * this.unit,-startNode.y * this.unit);
            if(dir == 0){
                this.animalTail.y -= this.animalAdjustDistance;
            }else if(dir == 1){
                this.animalTail.x -= this.animalAdjustDistance;
            }else if(dir == 2){
                this.animalTail.y += this.animalAdjustDistance;
            }else if(dir == 3){
                this.animalTail.x += this.animalAdjustDistance;
            }
            this.animalTail.setRotation([180,270,0,90][dir]);
        }
    },

    getDir(){  // 获取当前方向
        // 上右下左 0 1 2 3
        if(this.link.length == 1){
            return 2;
        }else{
            return this.link[this.link.length-1].dir;
        }
    },
    
    fadeCubes(index,callback){  // 缩回到某个节点
        if(callback && (this.link.length == 1 || index == this.link.length - 1)){
            callback();
        }
        if(index+1 >= this.link.length || this.isFading) return;

        this.isFading = true;
        console.log("回到第 "+ index +" 步");
        
        let _this = this;
        let animalBodies = this.animalBodies;
        let currentBody = null;

        let head = _this.link[_this.link.length-1];
        let iniX = null, iniY = null, iniDir = null;

        (function fade(){
            iniX = head._x;
            iniY = head._y;
            iniDir = head.dir;

            head.index = null;
            head.dir = null;

            currentBody = animalBodies[animalBodies.length-1];
            _this.animalBodiesPool.put(currentBody);
            animalBodies.length--;

            let theBody = animalBodies[animalBodies.length-1];
            theBody.width = 0;
            theBody.height = 0;
            if(animalBodies.length == 1){
                let startNode = _this.chapterData.startNode;
                theBody.width = _this.cubeSize;
                theBody.height = _this.cubeSize;
                theBody.setPosition(startNode.x * _this.unit, -startNode.y * _this.unit);
            }

            _this.link.length--;
            head = _this.link[_this.link.length-1];

            _this.animalHead.setRotation([180,270,0,90][_this.getDir()]);
            _this.headAdjust(iniDir, _this.getDir());

            _this.animalHead.runAction(cc.sequence(
                cc.moveTo(25/1000, _this.animalHead.x + (head._x - iniX)* _this.unit, _this.animalHead.y + (iniY - head._y)* _this.unit),
                cc.callFunc(()=>{
                    if(_this.link.length == index + 1){
                        _this.tailAdjust(2);
                        _this.isFading = false;
                        if(callback){
                            callback();
                        }
                    }else{
                        fade();
                    }
                })
            ));
        })();
    },

    restart(){  // 重开
        this.fadeCubes(0);
    },

    getResult(result){  // 获得答案
        STA.log("paintCubes - getResult");

        let _this = this;
        function getTheStep(){  // 逐步匹配，缩回第一个不同的那步
            let theStep = 0;
            for(let i=0,l=_this.link.length;i<l;i++){
                if(i == l-1){
                    if(_this.link[i]._x == result[i].x && _this.link[i]._y == result[i].y){
                        theStep = i;
                    }else{
                        theStep = i-1;
                    }
                }

                if(!(_this.link[i]._x == result[i].x && _this.link[i]._y == result[i].y)){
                    theStep = i-1;
                    break;
                }
            }

            if(_this.resultEnd - theStep < 3){
                _this.resultEnd = theStep + 3;
            }
            return theStep;
        }

        this.isTiping = true;
        let theStep = getTheStep();
        this.fadeCubes(theStep,()=>{
            let l = this.link.length;
            let head = this.link[l-1];
            let headX = null, headY = null;
    
            let theX = null, theY = null, theCube = null;
            let i = theStep;
            (function tiping(){
                if(i > _this.resultEnd || i > _this.winNumber - 1){
                    _this.resultEnd += 3;
                    if(_this.resultEnd > result.length - 2){
                        _this.resultEnd = result.length - 2;
                    }
                    _this.isTiping = false;
                    return;
                }
    
                headX = head._x;
                headY = head._y;
                
                theX = result[i].x;
                theY = result[i].y;
    
                STA.log(headX, headY);
                STA.log(theX, theY);
                STA.log();
    
                theCube = _this.map[theY][theX];
    
                // 计算方向
                if(headX == theX){
                    if(theY - headY == 1){
                        _this.moveToDir(theCube,2);
                    }else if(theY - headY == -1){
                        _this.moveToDir(theCube,0);
                    }
                }else if(headY == theY){
                    if(theX - headX == 1){
                        _this.moveToDir(theCube,1);
                    }else if(theX - headX == -1){
                        _this.moveToDir(theCube,3);
                    }
                }
    
                i++;
                head = theCube;
                _this.tipInterval = setTimeout(tiping,200);  // 如果定时器时间小于动物头的移动时间 ，则会导致动物头不完全移动
            })();
        });
    },

    start () {

    },
    
    onDestroy() {
        console.log("paintCubes - destroy");
        clearTimeout(this.tipInterval);
        clearTimeout(this.headWaitBlinkTimeout);         
        clearTimeout(this.gameWinTimeout);
    },
    
    update (dt) {

    },
});
